package org.forex.api.ws;

import java.io.BufferedReader;
import java.io.DataOutputStream;
import java.io.IOException;
import java.io.InputStreamReader;
import java.net.URL;
import java.util.HashMap;
import java.util.Map;
import java.util.Optional;

import javax.net.ssl.HttpsURLConnection;

import com.google.gson.Gson;

public abstract class AbstractHttpCall<T> {

	public static Map<String, String> headers;
	public static Gson gson;

	public static final String baseUrl="https://api-fxpractice.oanda.com";
	private final String USER_AGENT = "Mozilla/5.0";

	public static String GET="GET";
	public static String POST="POST";
	public static String DELETE="DELETE";

	static{
		headers=new HashMap<>();
		headers.put("Authorization", "Bearer 09d809e0c963493c9f6702917fee51df-02a690da64ae9d33946321659e766397");

		gson=new Gson();
	}

	public Class<T> clazz;

	public AbstractHttpCall(Class<T> clazz) {
		this.clazz=clazz;
	}

	public Optional<T> call(String url) throws IOException{
		BufferedReader in =null;
		try{

			StringBuffer sbUrl=new StringBuffer(baseUrl);
			sbUrl.append(url);
			StringBuffer parameters=new StringBuffer("1=1");

			if(getParameters()!=null && getParameters().size()>0){

				for(String s: getParameters().keySet()){
					parameters.append("&").append(s).append("=").append(getParameters().get(s));
				}
			}

			HttpsURLConnection con=null;

			switch(getHttpMethod()){
				case "GET":
					sbUrl.append("?").append(parameters);
					con=(HttpsURLConnection) new URL(sbUrl.toString()).openConnection();
					con.setRequestMethod(getHttpMethod());
					con.setRequestProperty("User-Agent", USER_AGENT);
					con.setConnectTimeout(30000);

					for(String k: headers.keySet()){
						con.addRequestProperty(k, headers.get(k));
					}
					break;
				case "POST":
					con=(HttpsURLConnection) new URL(sbUrl.toString()).openConnection();
					con.setDoInput(true);
					con.setDoOutput(true);
					con.setRequestMethod(getHttpMethod());
					con.setRequestProperty("User-Agent", USER_AGENT);
					con.setConnectTimeout(30000);

					for(String k: headers.keySet()){
						con.addRequestProperty(k, headers.get(k));
					}

					DataOutputStream wr = new DataOutputStream(con.getOutputStream());
					wr.writeBytes(parameters.toString());
					wr.flush();
					wr.close();
					break;
				case "DELETE":
					//sbUrl.append("?").append(parameters);
					con=(HttpsURLConnection) new URL(sbUrl.toString()).openConnection();
					con.setDoOutput(true);
					//con.setRequestProperty("Content-Type", "application/x-www-form-urlencoded" );
					con.setRequestMethod(getHttpMethod());
					con.setRequestProperty("User-Agent", USER_AGENT);
					con.setConnectTimeout(30000);

					for(String k: headers.keySet()){
						con.addRequestProperty(k, headers.get(k));
					}
					break;
			}

			in = new BufferedReader(new InputStreamReader(con.getInputStream()));

			return Optional.ofNullable(gson.fromJson(in, clazz));
		}finally{
			if(in!=null)
				try {
					in.close();
				} catch (IOException e) {
					// TODO Auto-generated catch block
					e.printStackTrace();
				}
		}


	}

	public abstract String getHttpMethod();

	public abstract Map<String, String> getParameters();
}
